// noipNOIp 视频1：25，分析很好，建议看一下
#include <bits/stdc++.h>
using namespace std;
#define debug(x) cerr << #x << "->" << x << endl;

const int MAXN = 20; // 最大人数限制
int a[MAXN];         // 存储每个人的糖果数量
int f[(1 << MAXN) + 3],
sum[(1 << MAXN) + 3]; // f[S]: 状态S的最大分段数，sm[S]: 状态S的糖果和
int last_person[(1 << MAXN) + 3]; // last_person[S]: 记录状态S的最后一个元素

int main() {
  
  int n;               // 实际人数
  scanf("%d", &n);
  int s = 0;
  for (int i = 0; i < n; ++i)
    scanf("%d", a + i), s += a[i]; //  求和

  // 检查糖果总数是否能被n整除
  if (s % n != 0) {
    puts("-1"); // 不能整除则无解
    return 0;
  }

  int avg = s / n; // 计算平均糖果数
  for (int i = 0; i < n; ++i)
    a[i] -= avg; // 将糖果数转换为与平均值的差值

  //  noipNOIp 视频1：25，分析很好，建议看一下
  //  | ----- |  ------ | -------| --------|
  // 对于每一种状态S，想象成前缀和，没遇到前缀和为0，就可以作为一个分段，
  // 因为前缀和为0，说明这段区间的糖果和为0，即可以作为一个分段

  // 状态压缩DP：枚举所有子集
  for (int S = 1; S < (1 << n); ++S) {
    for (int i = 0; i < n; ++i) {
      if ((S >> i) & 1) { // 如果第i个人在子集S中
        // i 作为贪心序列的最后一个位置
        sum[S] = sum[S ^ (1 << i)] + a[i]; // 计算子集S的糖果和
        int can = (sum[S] == 0);           // 如果和为0，可以作为一个分段
        if (f[S] <= f[S ^ (1 << i)] + can) {
          f[S] = f[S ^ (1 << i)] + can; // 更新最大分段数
          last_person[S] = i;           // 记录最后一个元素
        }
      }
    }
  }

  // 构建最优序列
  vector<int> p;              // 存储最优序列
  int now = (1 << n) - 1;     // 全集状态
  printf("%d\n", n - f[now]); // 输出需要的最小操作次数

  // 回溯构建序列
  while (now) {
    p.push_back(last_person[now]);  // 添加当前状态的最后一个元素
    now ^= (1 << last_person[now]); // 移除最后一个元素
  }
  reverse(p.begin(), p.end()); // 反转序列得到正确顺序

  // 运行贪心算法进行糖果分配
  for (int l = 0, r; l < p.size(); l = r + 1) {
    r = l;
    int tmp = a[p[l]]; // 当前分段的糖果和
    // 找到最小的连续分段，使得分段内糖果和为0
    while (tmp != 0) {
      ++r;
      tmp += a[p[r]];
    }
    // [l,r] 是贪心出来的最小一块和为0的区间

    // 在区间内找到第一个糖果数为负的位置作为中转站
    int neg = -1;
    for (int i = l; i <= r; ++i)
      if (a[p[i]] < 0) {
        neg = i;
        break;
      }

    // 第一步：将所有正数糖果转移到中转站
    for (int i = l; i <= r; ++i)
      if (a[p[i]] > 0 && i != neg) {
        printf("%d %d %d\n", p[i] + 1, p[neg] + 1, a[p[i]]); // 输出转移操作
        a[p[neg]] += a[p[i]];                                // 中转站接收糖果
        a[p[i]] = 0;                                         // 原位置糖果清空
      }

    // 第二步：从中转站分配糖果给所有负数位置
    for (int i = l; i <= r; ++i)
      if (a[p[i]] < 0 && i != neg) {
        printf("%d %d %d\n", p[neg] + 1, p[i] + 1, -a[p[i]]); // 输出分配操作
        a[p[neg]] += a[p[i]];                                 // 中转站减少糖果
        a[p[i]] = 0; // 目标位置糖果补足
      }
  }
  return 0;
}